#include "qtexteditappender.h"
#include <QThread>
#include <QMetaObject>
#include <QString>

QTextEditAppender::QTextEditAppender(LogLevel level, QTextEdit *textEdit)
    : BaseAppender(level),
    m_textEdit(nullptr),
    m_maxLines(1000),  // 默认最大1000行
    m_currentLines(0)
{
    // 初始化默认颜色（可动态修改）
    m_levelColors[LogLevel::Debug] = QColor(0x00,0xA0,0x00);    // Debug：绿色（适中亮度，避免刺眼）
    m_levelColors[LogLevel::Info] = QColor(0x00,0x66,0xCC);     // Info：蓝色（柔和蓝，清晰可见）
    m_levelColors[LogLevel::Warning] = QColor(0xFF,0xD7,0x00);  // Warning：黄色（暖黄，醒目不刺眼）
    m_levelColors[LogLevel::Error] = QColor(0xFF,0x33,0x33);    // Error：红色（稍暗红色，避免视觉疲劳）
    m_levelColors[LogLevel::Fatal] = QColor(0x99,0x00,0xCC);    // Fatal：紫色（亮紫，突出致命错误）

    if (textEdit)
        setTextEdit(textEdit);  // 关联输出组件
}

void QTextEditAppender::setTextEdit(QTextEdit *textEdit)
{
    QMutexLocker locker(&m_mutex);
    m_textEdit = textEdit;
    if (m_textEdit)
    {
        m_textEdit->setReadOnly(true);  // 日志窗口设为只读
        m_textEdit->setAcceptRichText(true);  // 启用富文本（默认开启，显式声明）
    }
}

void QTextEditAppender::setLevelColor(LogLevel level, const QColor &color)
{
    QMutexLocker locker(&m_mutex);
    m_levelColors[level] = color;
}

void QTextEditAppender::setMaxLines(int maxLines)
{
    QMutexLocker locker(&m_mutex);
    m_maxLines = maxLines;
}

void QTextEditAppender::append(LogLevel level, const QString& msg)
{
    // 1. 级别过滤：低于当前级别不处理
    if (level < m_level)
        return;

    // 2. 检查组件是否有效
    QMutexLocker locker(&m_mutex);
    if (!m_textEdit)
        return;

    // 3. 生成带颜色的HTML格式日志
    QColor color = m_levelColors[level];  // 获取当前级别对应的颜色
    QString colorName = color.name();     // 转换为HTML颜色格式（如"#FF0000"）

    // 转义特殊字符（如&、<、>等，避免破坏HTML结构）
    QString escapedMsg = msg.toHtmlEscaped();

    // 构造HTML：用span标签包裹，设置颜色+换行
    QString htmlMsg = QString("<span style='color:%1'>%2</span><br>").arg(colorName,escapedMsg);

    // 4. 复制参数到局部变量（避免跨线程访问问题）
    QTextEdit* textEdit = m_textEdit;
    int currentLines = m_currentLines;
    int maxLines = m_maxLines;

    // 5. 线程安全：如果当前线程不是UI线程，通过元对象系统调用
    if (QThread::currentThread() != textEdit->thread())
    {
        QMetaObject::invokeMethod(this,
                                  "doAppend",
                                  Qt::QueuedConnection,
                                  Q_ARG(QString, htmlMsg),
                                  Q_ARG(int, currentLines),
                                  Q_ARG(int, maxLines));
    }
    else
    {
        // 直接在UI线程执行
        doAppend(htmlMsg, currentLines, maxLines);
    }
}

void QTextEditAppender::doAppend(const QString& htmlMsg, int currentLines, int maxLines)
{
    QMutexLocker locker(&m_mutex);
    if (!m_textEdit)
        return;

    // 6. 检查行数限制：超过则清空
    if (maxLines > 0 && currentLines >= maxLines)
    {
        m_textEdit->clear();
        m_currentLines = 0;  // 重置行数计数
    }

    // 7. 追加HTML格式日志（带颜色）
    m_textEdit->insertHtml(htmlMsg);

    // 8. 自动滚动到底部（显示最新日志）
    m_textEdit->moveCursor(QTextCursor::End);

    // 9. 更新行数计数
    m_currentLines++;
}

